from app.api import api
from app.models import SysUser
from flask import request, jsonify, session, current_app
from flask_login import login_required, login_user, current_user, logout_user
from app import db
from datetime import timedelta


from PIL import Image, ImageDraw, ImageFont
import random
import io
import base64
import hashlib
import secrets


def get_md5(str):
    md5_hash = hashlib.md5()
    data_bytes = str.encode('utf-8')
    # 更新哈希对象，传入要加密的数据
    md5_hash.update(data_bytes)
    # 获取十六进制格式的哈希值
    hex_dig = md5_hash.hexdigest()
    return hex_dig


def generate_equation():
    """生成随机算式并返回算式文本和正确答案"""
    operator = random.choice(['+', '×'])

    if operator == '+':
      num1 = random.randint(0, 9)
      num2 = random.randint(0, 9)
      answer = num1 + num2
    else:
      num1 = random.randint(1, 9)
      num2 = random.randint(1, 9)
      answer = num1 * num2

    return f"{num1} {operator} {num2}", str(answer)


@api.route('/auth/captcha')
def captcha():
    # 生成算式和答案
    equation, answer = generate_equation()

    hex_dig = get_md5(answer)
    session["captcha"] = hex_dig  # 将验证码文本存储在会话中，以便后续验证

    # print(answer)
    # print(hex_dig)

    # 创建图片
    width = 120
    height = 38
    image = Image.new('RGB', (width, height), (255, 255, 255))
    draw = ImageDraw.Draw(image)

    # 尝试加载字体
    try:
      font = ImageFont.truetype('app/utils/fonts/Arial.ttf', 24)
    except IOError:
      font = ImageFont.load_default()

    # 绘制算式
    bbox = draw.textbbox((0, 0), equation, font=font)
    text_width = bbox[2] - bbox[0]
    text_height = bbox[3] - bbox[1]
    x = (width - text_width) / 2
    y = (height - text_height) / 2
    draw.text((x, y), equation, fill=(0, 0, 0), font=font)

    # 添加干扰线
    for _ in range(3):
      x1 = random.randint(0, width)
      y1 = random.randint(0, height)
      x2 = random.randint(0, width)
      y2 = random.randint(0, height)
      draw.line([(x1, y1), (x2, y2)], fill=(random.randint(50, 200), random.randint(50, 200), random.randint(50, 200)),
                width=1)

    # 创建响应
    img_io = io.BytesIO()
    image.save(img_io, 'PNG')
    img_io.seek(0)


    # 将字节流编码为base64字符串
    base64_str = base64.b64encode(img_io.getvalue()).decode('utf-8')

    # response = make_response(img_io.getvalue())
    # response.headers['Content-Type'] = 'image/png'
    # return response

    return jsonify(
      {'code': '00000', 'data': {'captchaKey': hex_dig, 'captchaBase64': 'data:image/png;base64,' + base64_str},
       'msg': '一切ok'})


def generate_token():
    """生成随机令牌"""
    return secrets.token_hex(32)


# @login_required
# def record_login_history(type):
#     online = OnLine()
#     online.ID = str(uuid.uuid4())
#     online.LOGINNAME = current_user.LOGINNAME
#     online.IP = request.remote_addr
#     online.TYPE = type
#     db.session.add(online)
#     db.session.commit()


# 登录接口
@api.route('/auth/login', methods=['POST'])
def login():
    try:
        session.permanent = True  # 确保这是一个持久的session
        # # 获取请求数据（以json格式提交时）
        # data = request.get_json()
        # 获取请求数据（以json格式提交时）
        data = request.form

        # 检查必需参数
        required_fields = ['username', 'password', 'captchaKey', 'captchaCode']
        if not all(field in data for field in ['username', 'password']):
            return jsonify({
                "code": "400",
                "data": None,
                "msg": "用户名或密码不能为空"
            }), 400

        if not all(field in data for field in ['captchaKey', 'captchaCode']):
            return jsonify({
                "code": "400",
                "data": None,
                "msg": "验证码不能为空"
            }), 400

        # 验证验证码
        captcha_key = data['captchaKey']
        user_captcha = data['captchaCode']

        session_captcha = session.get("captcha")  # 获取会话中的验证码文本

        if session_captcha != captcha_key or session_captcha != get_md5(user_captcha):
            return jsonify({
                "code": "400",
                "data": None,
                "msg": "验证码错误"
            }), 400


        # 验证用户
        username = data['username']
        password = data['password']
        remember_me = data.get('rememberMe', False)
        truthy_map = {"true": True, "false": False}
        if not isinstance(remember_me, bool):
            remember_me = truthy_map.get(remember_me.lower(), False)

        # 检查用户名是否存在(逻辑删除标识0未删除)
        user = SysUser.query.filter_by(username=username).first()

        if user is not None and user.verify_password(password):
            # 逻辑删除标识(0-未删除 1-已删除)
            if user.is_deleted != 0:
                return jsonify({
                    "code": "401",
                    "data": None,
                    "msg": "账号已作删除标记"
                }), 401

            # 状态(1-正常 0-禁用)
            if user.status != 1:
                return jsonify({
                    "code": "401",
                    "data": None,
                    "msg": "账号未激活"
                }), 401

            login_user(user, remember=remember_me, duration=timedelta(days=1))
            # record_login_history(1)
            # 生成令牌
            access_token = generate_token()
            refresh_token = generate_token()

            return jsonify({
                "code": "00000",
                "data": {
                    "tokenType": "Bearer",
                    "accessToken": access_token,
                    "refreshToken": refresh_token,
                    "expiresIn": 3600 * 2  # 2小时过期
                },
                "msg": "登录成功"
            })

        return jsonify({
            "code": "401",
            "data": None,
            "msg": "用户名或密码错误"
        }), 401

    except Exception as e:
        return jsonify({
            "code": "500",
            "data": None,
            "msg": f"服务器错误: {str(e)}"
        }), 500


# 刷新 token 接口
@api.route('/auth/refresh-token', methods=['POST'])
def refreshToken():
    pass

# 退出接口
@api.route('/auth/logout', methods=['DELETE'])
@login_required
def logout():
    logout_user()
    return jsonify({ "code": "00000", "data": {}, "msg": "退出成功"})



# 注册接口
@api.route('/auth/register', methods=['POST'])
def register():
    try:
        # # 获取请求数据（以json格式提交时）
        # data = request.get_json()
        # 获取请求数据（以json格式提交时）
        data = request.form

        # 检查必需参数
        required_fields = ['username', 'password', 'confirmPassword', 'captchaKey', 'captchaCode']
        if not all(field in data for field in ['username', 'password', 'confirmPassword']):
            return jsonify({
                "code": "400",
                "data": None,
                "msg": "用户名或密码不能为空"
            }), 400

        if not all(field in data for field in ['captchaKey', 'captchaCode']):
            return jsonify({
                "code": "400",
                "data": None,
                "msg": "验证码不能为空"
            }), 400

        # 验证验证码
        captcha_key = data['captchaKey']
        user_captcha = data['captchaCode']

        session_captcha = session.get("captcha")  # 获取会话中的验证码文本

        if session_captcha != captcha_key or session_captcha != get_md5(user_captcha):
            return jsonify({
                "code": "400",
                "data": None,
                "msg": "验证码错误"
            }), 400


        # 验证用户
        username = data['username']
        password = data['password']
        confirmPassword = data['confirmPassword']
        remember_me = data.get('rememberMe', False)

        # 检查用户名是否存在
        user = SysUser.query.filter_by(username=username).first()

        if user is not None:
            return jsonify({
                "code": "400",
                "data": None,
                "msg": "用户名已被占用"
            }), 400

        # 检查两次密码是否一致
        if password != confirmPassword:
            return jsonify({
                "code": "400",
                "data": None,
                "msg": "两次密码不一致"
            }), 400

        user = SysUser(username=username, password=password, status=0)
        db.session.add(user)
        db.session.commit()
        return jsonify({"code": "00000", "data": {}, "msg": "注册成功"})

    except Exception as e:
        return jsonify({
            "code": "500",
            "data": None,
            "msg": f"服务器错误: {str(e)}"
        }), 500


